﻿using HelixToolkit.Wpf;
using System;
using System.Windows.Data;
using System.Windows.Media;
using System.Windows.Media.Media3D;

namespace Minecraft_Armor_Stand_Creater.Resource.Models
{
    class ArmorStand
    {
        static readonly string wood_path = new Uri("pack://application:,,,/Resource/Textures/wood.png").ToString();
        static readonly string stone_path = new Uri("pack://application:,,,/Resource/Textures/stone.png").ToString();

        public ArmorStand()
        {

        }

        /// <summary>
        /// 获取整个盔甲架
        /// </summary>
        /// <returns></returns>
        public static ModelVisual3D GetArmorStand()
        {
            ModelVisual3D armor_stand = new ModelVisual3D()
            {
                Transform = new TranslateTransform3D()
                {
                    OffsetZ = 19.5//以底座为坐标原点
                }
            };

            ModelVisual3D rotable_part = new ModelVisual3D()
            {
                Transform = new RotateTransform3D()
                {
                    Rotation = new AxisAngleRotation3D()
                    {
                        Axis = new Vector3D(0, 0, 1),
                        Angle = 0
                    }
                }
            };

            rotable_part.Children.Add(GetHead());
            rotable_part.Children.Add(GetBody());
            rotable_part.Children.Add(GetLeftArm());
            rotable_part.Children.Add(GetRightArm());
            rotable_part.Children.Add(GetLeftLeg());
            rotable_part.Children.Add(GetRightLeg());
            armor_stand.Children.Add(rotable_part);
            armor_stand.Children.Add(GetPlate());

            return armor_stand;
        }

        /// <summary>
        /// 获取头部
        /// </summary>
        /// <returns></returns>
        static ModelVisual3D GetHead()
        {
            ModelVisual3D as_head = new ModelVisual3D();
            BoxVisual3D model_head = new BoxVisual3D()
            {
                Length = 2,
                Width = 2,
                Height = 8,
                Center = new Point3D(0, 0, 3),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            as_head.Children.Add(model_head);
            //朝向控制器
            RotateManipulator[] rotateManipulators = GetRotateManipulators(model_head, 9, 8);
            for (int i = 0; i < rotateManipulators.Length; i++)
                as_head.Children.Add(rotateManipulators[i]);

            return as_head;
        }

        /// <summary>
        /// 获取躯干
        /// </summary>
        /// <returns></returns>
        static ModelVisual3D GetBody()
        {
            ModelVisual3D as_body = new ModelVisual3D();
            ModelVisual3D model_body = new ModelVisual3D();
            #region Children in model_body
            BoxVisual3D body1 = new BoxVisual3D()
            {
                Length = 3,
                Width = 12,
                Height = 3,
                Center = new Point3D(0, 0, 0),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            BoxVisual3D body2 = new BoxVisual3D()
            {
                Length = 2,
                Width = 2,
                Height = 7,
                Center = new Point3D(0, 2, -3.5),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            BoxVisual3D body3 = new BoxVisual3D()
            {
                Length = 2,
                Width = 2,
                Height = 7,
                Center = new Point3D(0, -2, -3.5),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            BoxVisual3D body4 = new BoxVisual3D()
            {
                Length = 2,
                Width = 8,
                Height = 2,
                Center = new Point3D(0, 0, -7),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            model_body.Children.Add(body1);
            model_body.Children.Add(body2);
            model_body.Children.Add(body3);
            model_body.Children.Add(body4);
            #endregion
            as_body.Children.Add(model_body);
            //朝向控制器
            RotateManipulator[] rotateManipulators = GetRotateManipulators(model_body, 11, 10);
            for (int i = 0; i < rotateManipulators.Length; i++)
                as_body.Children.Add(rotateManipulators[i]);

            return as_body;
        }

        /// <summary>
        /// 获取左臂
        /// </summary>
        /// <returns></returns>
        static ModelVisual3D GetLeftArm()
        {
            ModelVisual3D as_left_arm = new ModelVisual3D()
            {
                Transform = new TranslateTransform3D()
                {
                    OffsetY = 6
                }
            };
            BoxVisual3D model_left_arm = new BoxVisual3D()
            {
                Length = 2,
                Width = 2,
                Height = 12,
                Center = new Point3D(0, 0, -4.5),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            as_left_arm.Children.Add(model_left_arm);

            //朝向控制器
            RotateManipulator[] rotateManipulators = GetRotateManipulators(model_left_arm, 11, 10);
            for (int i = 0; i < rotateManipulators.Length; i++)
                as_left_arm.Children.Add(rotateManipulators[i]);

            return as_left_arm;
        }

        /// <summary>
        /// 获取右臂
        /// </summary>
        /// <returns></returns>
        static ModelVisual3D GetRightArm()
        {
            ModelVisual3D as_right_arm = new ModelVisual3D()
            {
                Transform = new TranslateTransform3D()
                {
                    OffsetY = -6
                }
            };
            BoxVisual3D model_right_arm = new BoxVisual3D()
            {
                Length = 2,
                Width = 2,
                Height = 12,
                Center = new Point3D(0, 0, -4.5),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            as_right_arm.Children.Add(model_right_arm);

            //朝向控制器
            RotateManipulator[] rotateManipulators = GetRotateManipulators(model_right_arm, 11, 10);
            for (int i = 0; i < rotateManipulators.Length; i++)
                as_right_arm.Children.Add(rotateManipulators[i]);

            return as_right_arm;
        }

        /// <summary>
        /// 获取左腿
        /// </summary>
        /// <returns></returns>
        static ModelVisual3D GetLeftLeg()
        {
            ModelVisual3D as_left_leg = new ModelVisual3D()
            {
                Transform = new TranslateTransform3D()
                {
                    OffsetY = 2,
                    OffsetZ = -7
                }
            };
            BoxVisual3D model_left_leg = new BoxVisual3D()
            {
                Length = 2,
                Width = 2,
                Height = 13,
                Center = new Point3D(0, 0, -5.5),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            as_left_leg.Children.Add(model_left_leg);

            //朝向控制器
            RotateManipulator[] rotateManipulators = GetRotateManipulators(model_left_leg, 8, 7);
            for (int i = 0; i < rotateManipulators.Length; i++)
                as_left_leg.Children.Add(rotateManipulators[i]);

            return as_left_leg;
        }

        /// <summary>
        /// 获取右腿
        /// </summary>
        /// <returns></returns>
        static ModelVisual3D GetRightLeg()
        {
            ModelVisual3D as_right_leg = new ModelVisual3D()
            {
                Transform = new TranslateTransform3D()
                {
                    OffsetY = -2,
                    OffsetZ = -7
                }
            };
            BoxVisual3D model_right_leg = new BoxVisual3D()
            {
                Length = 2,
                Width = 2,
                Height = 13,
                Center = new Point3D(0, 0, -5.5),
                Material = MaterialHelper.CreateImageMaterial(wood_path)
            };
            as_right_leg.Children.Add(model_right_leg);

            //朝向控制器
            RotateManipulator[] rotateManipulators = GetRotateManipulators(model_right_leg, 8, 7);
            for (int i = 0; i < rotateManipulators.Length; i++)
                as_right_leg.Children.Add(rotateManipulators[i]);

            return as_right_leg;
        }

        /// <summary>
        /// 获取底座
        /// </summary>
        /// <returns></returns>
        static ModelVisual3D GetPlate()
        {
            ModelVisual3D as_plate = new ModelVisual3D();
            BoxVisual3D model_plate = new BoxVisual3D()
            {
                Length = 12,
                Width = 12,
                Height = 1,
                Center = new Point3D(0, 0, -19.5),
                Material = MaterialHelper.CreateImageMaterial(stone_path)
            };

            as_plate.Children.Add(model_plate);

            return as_plate;
        }

        /// <summary>
        /// 获取朝向控制器
        /// </summary>
        /// <param name="Target">目标元素</param>
        /// <param name="diameter">外环</param>
        /// <param name="innerDiameter">内环</param>
        /// <returns></returns>
        static RotateManipulator[] GetRotateManipulators(ModelVisual3D Target, double diameter, double innerDiameter)
        {
            RotateManipulator[] manipulators = new RotateManipulator[3];

            manipulators[0] = new RotateManipulator() //X
            {
                Axis = new Vector3D(1, 0, 0),
                Color = Colors.Red,
                Diameter = diameter,
                InnerDiameter = innerDiameter
            };
            manipulators[1] = new RotateManipulator() //Y
            {
                Axis = new Vector3D(0, 1, 0),
                Color = Colors.Green,
                Diameter = diameter,
                InnerDiameter = innerDiameter
            };
            manipulators[2] = new RotateManipulator() //Z
            {
                Axis = new Vector3D(0, 0, 1),
                Color = Colors.Blue,
                Diameter = diameter,
                InnerDiameter = innerDiameter
            };

            for (int i = 0; i < manipulators.Length; i++)
            {
                //BindingOperations.SetBinding(Target, ModelVisual3D.TransformProperty, new Binding("Transform") { Source = manipulators[i] });
                BindingOperations.SetBinding(manipulators[i],
                    Manipulator.TargetTransformProperty,
                    new Binding("Transform")
                    {
                        Mode = BindingMode.TwoWay,
                        Source = Target
                    });
            }

            return manipulators;
        }
    }
}
